/*!
 *  \file       SimpleRawImage.cpp
 *  \brief      Implementazione della classe \c SimpleRawImage
 *  \author     Davide Scola <S2299453@studenti.unige.it>
 *  \author	Minetti Alberto <S3064777@studenti.unige.it>
 *  \version    1.0
 *
 */
#include <vector>
#include <fstream>
#include "SimpleMatrix.hpp"
#include "SimpleRawImage.hpp"
#include "FileException.cpp"
#include "NotExistingFileException.cpp"
#include "NotReadableFileException.cpp"
#include "NotWritableFileException.cpp"
#include "FileWriteException.cpp"
#include "InvalidFileSizeException.cpp"



using namespace std;


/*!
 *  \brief      Costruttore di \c SimpleRawImage
 *  \param[in]	numRows		il numero di righe
 *  \param[in]	numCols		il numero di colonne
 *
 *  \exception InvalidSizeException	se almeno una delle due dimensioni e` nulla
 */
template < class tType >
SimpleRawImage< tType >::SimpleRawImage( const unsigned int numRows, const unsigned int numCols )
    : SimpleMatrix< tType >( numRows, numCols )
{
}

/*!
 *  \brief	Importa il contenuto dell'immagine da un file
 *
 *  \param[in]	fname	nome del file da cui importare
 *
 *	\exception	NotExistingFileException	sollevata se il file non e' esistente
 *	\exception	NotReadableFileException	sollevata se il file non e' leggibile
 *	\exception	InvalidFileSizeException	sollevata se la dimensione del file e' errata
 */
template< class tType > void
SimpleRawImage< tType >::importFromFile( const char *fname )
{
  fstream input( fname, std::ios_base::binary | std::ios_base::in );
  if( !input ) {
	throw NotExistingFileException( );
  }
  if( !input.is_open() || !input.good() ) {
	throw NotReadableFileException( );
  }
  
  if( input.read( reinterpret_cast< char * >(&this->data_[0]), this->data_.size() * sizeof( tType ) ) ) {
	if( input.gcount() < 0 || ( unsigned long int )input.gcount() != this->getRows() * this->getCols() * sizeof( tType ) ) {
		throw InvalidFileSizeException( );
	}
  }
  input.close();
}

/*!
 *  \brief	Esporta il contenuto dell'immagine su un file
 *
 *  \param[in]	fname						nome del file su cui esportare
 *
 *	\exception	NotExistingFileException	sollevata se il file non e' esistente
 *	\exception	NotWritableFileException	sollevata se il file non e' scrivibile
 *	\exception	FileWriteException			sollevata se la write sul file fallisce
 */
template< class tType > void
SimpleRawImage< tType >::exportToFile( const char *fname )
{
  // controllare che il file esista, che si riesca ad aprirlo che la dimensione sia corretta, ecc. ecc.
  fstream output( fname, std::ios_base::binary | std::ios_base::out );
  if( !output ) {
	throw NotExistingFileException( );
  }
  if( !output.is_open() || !output.good() ) {
	throw NotWritableFileException( );
  }
  output.write( reinterpret_cast< char * >(&this->data_[0]), this->data_.size() * sizeof( tType ) );
  if( output.fail() ) {
	throw FileWriteException();
  }
  output.close();
}
